home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Aminet 1 (Walnut Creek)
/
Aminet - June 1993 [Walnut Creek].iso
/
aminet
/
util
/
misc
/
ddli2_02.lha
/
qst.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-04-04
|
3KB
|
154 lines
/* QST.C Copyright (C) 1993 Fergus Patrick Duniho */
#define MAXLINE 256
typedef struct qnode {
int p[2];
int num, ans, first;
char *Qtext, *Atext[2];
struct qnode *pv, *nx;
} qst;
qst *RND_QList (qst *Q, int size);
char *Get_QList (char *fname, qst *Q, int size);
void AskQuestions (qst *Q, int col);
int AskQ (qst *Q, int col);
char get_answer(int col);
qst *new_qnode (int num);
qst *new_qnode (int num) {
qst *node;
if ((node = (qst *)malloc(sizeof(qst))) == NULL) {
perror ("Malloc can't allocate enough memory for a new qnode.\n");
exit (2);
}
node->ans = -1;
node->num = num;
return node;
}
/* Get_QList: Reads questions from a file into a linked list.
Returns the version # string from the beginning of the
questions file. */
char *Get_QList (char *fname, qst *Q, int size) {
FILE *fptr;
int i, j;
char *V;
qst *S;
S = Q;
RdOpen (fptr, fname);
V = clone_line(fptr, MAXLINE);
for (i = 1; i <= size; i++) {
Q->nx = new_qnode(i);
Q->nx->pv = Q;
Q = Q->nx;
Q->Qtext = clone_line(fptr, MAXLINE);
for (j = 0; j < 2; j++) {
Q->p[j] = fgetp(fptr);
Q->Atext[j] = clone_line(fptr, MAXLINE);
}
}
fclose (fptr);
Q->nx = S;
return V;
}
/* nth_qnode: Returns the nth member of a linked list of qst nodes. */
qst *nth_qnode (qst *Q, unsigned int n) {
while (n--)
Q = Q->nx;
return Q;
}
/* RND_QList: Randomizes a linked list of questions. */
qst *RND_QList (qst *Q, int size) {
qst *S, *L, *N, *SN;
unsigned int i;
SN = N = new_qnode(0); /* Randomizes Question Order */
S = Q;
for (; size; size--) {
i = (rand() % size) + 1;
L = nth_qnode(S, i);
L->nx->pv = L->pv;
L->pv->nx = L->nx;
N->nx = L;
L->pv = N;
N = L;
N->first = rand() % 2; /* Randomizes Answer Order */
}
free (S);
N->nx = SN;
SN->pv = N;
return SN;
}
void AskQuestions (qst *Q, int col) {
int more = 1, flag = 1, num;
while (more) {
for (Q = Q->nx, num = 1; Q->num > 0; Q = Q->nx, num++) {
if ((Q->ans != -1) && flag)
continue;
flag = 1;
printf ("\nQuestion #%d\n", num);
if (AskQ(Q, col)) {
Q = Q->pv->pv;
flag = 0;
num -= 2;
if (num < 0) num = 0;
}
}
more = 0;
for (Q = Q->nx; Q->num > 0; Q = Q->nx)
if (Q->ans == -1) more = 1;
}
}
/* AskQ: Asks a single question. */
int AskQ (qst *Q, int col) {
char A;
wrapwrite (stdout, 0, 0, col, Q->Qtext, 0);
wrapwrite (stdout, 0, 4, col, "(A)", Q->Atext[0], 0);
puts (" ... Or");
wrapwrite (stdout, 0, 4, col, "(B)", Q->Atext[1], 0);
if ((A = get_answer(col)) < 2)
Q->ans = Q->p[A];
else if (A == 4)
exit (2);
return A == 3;
}
char get_answer(int col) {
char c;
for (;;) {
c = fgetc(stdin);
while (fgetc(stdin) != '\n');
if (islower(c))
c = toupper(c);
if (c == 'A')
return 0;
if (c == 'B')
return 1;
if (c == 'S')
return 2;
if (c == 'P')
return 3;
if (c == 'Q')
return 4;
wrapwrite (stdout, 0, 0, col,
"Answer with an A or a B.\n",
"P = Go back to Previous question\n",
"Q = Quit\n",
"S = Skip until later.\n", 0);
}
}